<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html lang="en" dir="ltr">
<head>
</head>
<body>
	
	
	
 
<link rel='stylesheet' type='text/css' href='./jsxgraph.css' />
<script src='./jsxgraphcore.js' type='text/javascript'></script>
<script src='./GeonextReader.min.js' type='text/javascript'></script>

<div id='box0' class='jxgbox' style='width:600px; height:600px;'></div>


<form><textarea id="inputtext0" rows=15 cols=35 wrap="off" style="width:600px;">
var level = 5;
var axiom = 'X';
var rules = {
    'F' : 'FF',
    'X' : new stocasticRule([
               {rule:'F-[[X]+X]+F[+FX]-X',probability:0.5},
               {rule:'F+[[X]+F]+F[+FX]-X',probability:0.5}
          ]),
    '[' : '[',
    ']' : ']',
    '+' : '+',
    '-' : '-'
};
var symbols = { 'F':'F',
                'X':' ',
                '+':'+',
                '-':'-',
                '[':'[',
                ']':']'
              } ;
              
var angle = 22.5;
var len = 200/Math.pow(2,level);
t.setPos(0,-250);
t.setProperty({strokeColor:'green',strokeWidth:1});


</textarea><br />
<input type="button" value="run" onClick="run(0)">
<input type="button" value="clear" onClick="clearturtle(0)">
</form>

<script type='text/javascript'>
var t;
var turtle = [];
var brd = [];
brd[0] = JXG.JSXGraph.initBoard('box0', {boundingbox: [-300, 300, 300, -300]});
turtle[0] = brd[0].create('turtle');


/* Verifica a lista de probabilidades passadas, qual sera utilizada, de acordo com
 um sorteio aleatorio */
function stocasticRule( rulesAndProbabilitues){
	
	this.rulesAndProbabilitues = rulesAndProbabilitues;
	
	this.normalizeProb = function(){};
	this.get = function (){
		var randVal = Math.random(); 
		var nowVal = 0;
		for (var i = 0; i < this.rulesAndProbabilitues.length; i++){
			nowVal += this.rulesAndProbabilitues[i].probability;
			if (nowVal >  randVal){
				return this.rulesAndProbabilitues[i].rule;
			}
		}
		//safe guard
		return this.rulesAndProbabilitues[0].rule;
		
	}
}

function expander(level,axiom,rules) {
    this.axiom = axiom;
    this.rules = rules;
    this.source = (level>1) ? new expander(level-1,axiom,rules) : (new function() {
        // Axiom:
        this.code = axiom;
        this.pos = 0;
        this.next = function() {
            if (this.pos>=this.code.length) return null;
            return this.code.charAt(this.pos++);
        }
    });
    
    this.code = '';
    this.pos = 0;
    this.next = function() {
        while (this.pos>=this.code.length) { // produce new symbols from source
            this.pos = 0;
            var pattern = this.source.next();
            if (!pattern) return null // Finished
     
			if (this.rules[pattern].get == null){
				//nao eh estocastico
				this.code = this.rules[pattern];
			}else{
				//eh estocastico
				this.code = this.rules[pattern].get();
			}
        }
        return this.code.charAt(this.pos++);
    }
}

/* Interpreta os simbolos de producao e gera a imagem */
function plotter(level,generator,symbols,len,angle,t,shrink) {

	var width = level;

    for (var c; c=generator.next(); c) {
        switch(symbols[c]) {
            case 'F':
                t.fd(len);
                break;
            case 'f':
                t.penUp();
                t.fd(len);
                t.penDown();
                break;
            case '+':
                t.lt(angle);
                break;
            case '-':
                t.rt(angle);
                break;
            case '[':
                t.pushTurtle();
                len *= shrink;
                break;
            case ']':
                t.popTurtle();
                len /= shrink;
                break;
            default:
                ;
        }
		width -= 1;
    }
    return null;
  }
var shrink = 1.0;
 
 /* Execucao do algoritmo para geracao do fractal */
function run(nr) {
  brd[nr].suspendUpdate();
  var code = document.getElementById('inputtext'+nr).value;
  if (code=='') { return; }
  t = turtle[nr];
  t.cs();
  t.hideTurtle();
  eval(code);
  var generator = new expander(level,axiom,rules);
  plotter(level,generator,symbols,len,angle,t,shrink);
  brd[nr].unsuspendUpdate();
}

function clearturtle(nr) {
  turtle[nr].cs();
}

</script>

</body></html>